package kin.serviceIMP.security;


import java.io.Serializable;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Set;

import javax.inject.Inject;



import org.hibernate.Criteria;
import org.hibernate.Query;
import org.hibernate.criterion.Restrictions;
import org.springframework.security.core.GrantedAuthority;

import org.springframework.security.core.authority.SimpleGrantedAuthority;

import org.springframework.security.core.userdetails.UserDetails;

import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import kin.bean.security.Role;
import kin.bean.security.User;
import kin.bean.security.UsersRoles;
import kin.bean.system.Result;
import kin.manager.security.UserManager;
import kin.service.security.UserServiceManager;




@Service
public class UserServiceManagerIMP implements UserServiceManager{
@Inject
private UserManager userManager;
	

	public UserManager getUserManager() {
		return userManager;
	}
	
	
	public void setUserManager(UserManager userManager) {
		this.userManager = userManager;
	}
	@Transactional(readOnly=true)
	public UserDetails loadUserByUsername(String username)
			throws UsernameNotFoundException {
		System.out.println("username:"+username);
		User u=this.findByUsername(username);
		if(null==u){
			throw  new UsernameNotFoundException("invail username");
		}else{
	       Collection<GrantedAuthority> grantedAuths = this.obtionGrantedAuthorities(u);
            return new org.springframework.security.core.userdetails.User(u.getUsername(), u.getPassword(), grantedAuths);
		}
	}
	
	
	private Set<GrantedAuthority> obtionGrantedAuthorities(User u) {
		
	    List<Role> rs=this.findRolesByUser(u.getUser_id());
		Set<GrantedAuthority> authorities=new HashSet<GrantedAuthority>();
			for(Role sr:rs){
			authorities.add(new SimpleGrantedAuthority(sr.getRole_name()));
			}
		return authorities;
	}

	
	
	public User login(User user) {
		LinkedHashMap<String,Object> where=new LinkedHashMap<String,Object>();
		where.put("username",user.getUsername());
		where.put("password",user.getPassword());
		try {
		 user=(User) this.userManager.find(where, null, null);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return user;
	}

	public boolean usernameExist(String  username){
		
	this.findByUsername(username);
	
	return true;
	}

	public List<Role> findRolesByUser(int userId) {
		User user=this.load(userId);
		
		Query q=this.userManager.getSessionFactory().getCurrentSession().createQuery("from UsersRoles u where u.user=?").setParameter(0, user);
		
		List<UsersRoles> l=q.list();
		
		List<Role> rs=new ArrayList<Role>();
		
	    for(UsersRoles ur:l){
	    	
	    	rs.add(ur.getRole());
	    	
	    }
		
		return rs;
	}

	public void addOrUpdateRoleByUser(User user, Role role,int usersroles_orderNo) throws Exception{
		
		UsersRoles ur=null;
		
		ur=(UsersRoles) this.userManager.getSessionFactory().getCurrentSession().createQuery("from UsersRoles u where u.user=? and u.role=?").setParameter(0, user).setParameter(1, role).uniqueResult();
		
		if(ur!=null){
			 
			ur.setUsersroles_orderNo(usersroles_orderNo);
			
		}else{
			
			 ur=new UsersRoles();
			 
			 ur.setUser(user);
			 
			 ur.setRole(role);
			 
			 ur.setUsersroles_orderNo(usersroles_orderNo);
			 
		}
		this.userManager.getSessionFactory().getCurrentSession().saveOrUpdate(ur);
	}

	public void deleteRoleByUser(int userId, int roleId) {
		UsersRoles ur=null;
		ur=(UsersRoles) this.userManager.getSessionFactory().getCurrentSession().createQuery("from UsersRoles u where u.user.user_id=? and u.role.role_id=?").setParameter(0, userId).setParameter(1, roleId).uniqueResult();
		if(ur!=null){
		this.userManager.getSessionFactory().getCurrentSession().delete(ur);
		}
		
	}

	public User findByUsername(String username) {
		
		Criteria cra = null;
		cra =this.userManager.getSessionFactory().getCurrentSession().createCriteria(User.class);
		 cra.add(Restrictions.eq("username", username));
		return (User) cra.uniqueResult();
		
	}

	

	

	public List<User> findAll() {
		// TODO Auto-generated method stub
		return null;
	}

	public List<User> findList(LinkedHashMap<String, Object> where,
			LinkedHashMap<String, Collection> in,
			LinkedHashMap<String, Boolean> orderby) throws Exception {
		
		return null;
	}

	public Result findPaging(LinkedHashMap<String, Object> where,
			LinkedHashMap<String, String[]> in,
			LinkedHashMap<String, Boolean> orderby, int page, int start, int max)
			throws Exception {
		// TODO Auto-generated method stub
		return null;
	}

	public void add(User entity) throws Exception {
		this.userManager.add(entity);
		
	}



	

	

	

	public User load(int id) {
		return  (User) this.userManager.get(id);
		
	}


	
	public void update(User user) {
		this.update(user);
		
	}


	public void delete(Serializable entityId) throws Exception {
		this.userManager.delete(entityId);
		
	}




	

}
